package polarizedMF;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import labeling.LabelingBig;
import model.MFBig;
import model.PredictBig;
import data.DataBig;
import data.MatrixSize;
import data.Param;
import file.ParserBig;

public class Step0_TraditionalMF {

	/**
	 * @param args
	 * @throws IOException 
	 */
	double normalRMSE;
	double idealRMSE;
	
	public Step0_TraditionalMF(String dataset, double epsilon, String fold, MatrixSize size, Param param) throws IOException {
		String dir = dataset+"fold-"+fold+"\\";
		String trainFile = "train"+fold+"";
		String testFile = "test"+fold+"";
		int maxuid = size.getMaxuid();
		int maxiid = size.getMaxiid();
		
		ParserBig trainParser = new ParserBig(dir+trainFile);
		System.out.println(trainParser.getMaxuid()+" "+trainParser.getMaxiid());
		List<DataBig> trainData = trainParser.getList();
		
		ParserBig testParser = new ParserBig(dir+testFile);
		System.out.println(testParser.getMaxuid()+" "+testParser.getMaxiid());
		List<DataBig> testData = testParser.getList();
		
		List<DataBig> wholeData = new ArrayList<DataBig>();
		wholeData.addAll(trainData);
		wholeData.addAll(testData);
		
		byte k = param.getK();
		double gamma = param.getGamma();
		double lambda = param.getLambda();
		
		MFBig mf = new MFBig(trainData, maxuid, maxiid, k, gamma, lambda);
		PredictBig normalPredict = new PredictBig(testData, mf);
		this.normalRMSE = normalPredict.getAllRMSE();
		System.out.println("Normal MF RMSE: "+normalPredict.getAllRMSE());

		LabelingBig trainLabel = new LabelingBig(trainData, mf.getAvgTrain(), mf.getUbias(), mf.getIbias(), epsilon);
		LabelingBig testLabel = new LabelingBig(testData, mf.getAvgTrain(), mf.getUbias(), mf.getIbias(), epsilon);
		
		MFBig pmf = new MFBig(trainLabel.getPos(), maxuid, maxiid, k, gamma, lambda);
		MFBig nmf = new MFBig(trainLabel.getNeg(), maxuid, maxiid, k, gamma, lambda);
		
		PredictBig positive = new PredictBig(testLabel.getPos(), pmf);
		PredictBig negative = new PredictBig(testLabel.getNeg(), nmf);
		PredictBig neutral = new PredictBig(testLabel.getNeu(), mf);
		PredictBig whole = new PredictBig(testLabel.getPos(), testLabel.getNeg(), testLabel.getNeu(), mf, pmf, nmf);
		
		this.idealRMSE = whole.getAllRMSE();

		System.out.printf("Ideal MF RMSE on positive/neutral/negative/whole: %.3f / %.3f / %.3f / %.3f\n", 
				positive.getAllRMSE(), neutral.getAllRMSE(), negative.getAllRMSE(), whole.getAllRMSE());
	}

	public double getNormalRMSE() {
		return normalRMSE;
	}

	public double getIdealRMSE() {
		return idealRMSE;
	}
}
